#!/usr/bin/python

############################################
#
#  Downloader for Picasa
#
#
#  http://code.google.com/p/cens-image-feature-viz/
#
############################################
"""This downloader allows automated downloading of files 
to Picasa Web Albums.  It requires a valid Google account.
	
	Sample:
    
"""
__author__ = u'thisismike04@gmail.com' #'Mike Wilson'
__license__ = 'Apache License v2'
__version__ = 'Revision 16'


import gdata.photos, gdata.photos.service
import sys, os, getopt, getpass, urllib
from tools import client

def gather_arguments(argv):
###################################
#  Builds a dict out of the arguments
###################################
	
	state = {}

	if (len(argv) < 1):
		usage()
		sys.exit(2)
	
	try:
		opts, args = getopt.getopt(argv, "hd:p:a:u:s:", ["help", "user", "debug"])
	except getopt.GetoptError:          
			usage()                         
			sys.exit(2)                     
	for opt, arg in opts:
		if opt in ("-h", "--help"):
			usage()                     
			sys.exit(1)                  
		elif opt == '-d':
			if not os.path.isdir(arg):
				print('%s is not a directory') % arg
				sys.exit(1)
			if os.path.isfile(arg):
				print('%s is a file. Cannot create it as a directory.') % arg
				sys.exit(1)
			state["_dir"] = arg                   
		elif opt == '-p':
			state["_photo"] = arg
		elif opt == '-s':
			state['_pass'] = arg
		elif opt == '-a':
			state["_album"] = arg
		elif opt in ("-u", "--user"):
			state["_user"] = arg
		elif opt == "--debug":
			state["_debug"] = 0
		else:
			usage()
			sys.exit(1)
	
	if not state.has_key("_user"):
		state["_user"] = raw_input('Username: ')
	if not state.has_key("_photo") and not state.has_key("_album"):
		print('Please provide album, photo identifier, or both.');
		sys.exit(1)

	return state


class Downloader:
	def __init__(self, client, arguments):
		self.client = client
		self.args = arguments
		if not self.args.has_key("_dir"):
			self.args["_dir"] = os.path.abspath('.')
		self.albumEntry = None
		self.photoEntries = [ ]

	def getPhotoEntries(self):
		
		if self.args.has_key('_album') and self.args.has_key('_photo'):	
			self.getPhotoInAlbum()
		elif self.args.has_key('_album'):
			self.getAllInAlbum()
		else:
			self.getPhotos()
		
	def getPhotoInAlbum(self):
		self.getAlbum()
		user = self.args['_user']
		feedUri = 'http://picasaweb.google.com/data/feed/api/user/'+ user +\
				'/album/'+ self.albumEntry.title.text+'?kind=photo&q=' +\
				self.args['_photo']
 		self.getAllPhotosFromFeed(feedUri)
		
	def getAllInAlbum(self):
		self.getAlbum()
		user = self.args['_user']
		feedUri = 'http://picasaweb.google.com/data/feed/api/user/'+ user +\
				'/album/'+ self.albumEntry.title.text+'?kind=photo'
		self.getAllPhotosFromFeed(feedUri)

	def getPhotos(self):
		user = self.args['_user']
		feedUri = 'http://picasaweb.google.com/data/feed/api/user/'+ user+\
				'?kind=photo&q=' + self.args['_photo']
		self.getAllPhotosFromFeed(feedUri)

		
	def getAlbum(self):
		albumuri = 'http://picasaweb.google.com/data/feed/api/user/'+self.args['_user']+'?kind=album'
		UserFeed = self.client.GetFeed(albumuri)
		
		for album in UserFeed.entry:
			if album.title.text == self.args['_album']:
				self.albumEntry = album
				return
		print 'Album %s not found.' % self.args['_album']
		sys.exit(1)
	
	def getAllPhotosFromFeed(self, feedUri):
		if self.args.has_key('_debug'):
			print 'Getting all photos from %s' % feedUri
		photoFeed = self.client.GetFeed(feedUri)
		for photoentry in photoFeed.entry:
			if self.args.has_key('_debug'):
				print 'Fetching %s' % photoentry.title.text
			self.photoEntries.append(photoentry)

	def getAllImages(self):
		for entry in self.photoEntries:
			self.getImage(entry)
	

	def getImage(self, photoentry):
		photoUri = photoentry.content.src
		print 'Downloading %s' % photoentry.title.text
		if self.args.has_key('_debug'):
			print 'PhotoURI = %s' % photoUri

		filename = self.args['_dir'] +'/'+ photoUri.split('/')[-1]
		if os.path.isfile(filename):
			print '%s exists. Skip download?' % filename
			skip = (raw_input ('yes/no? ')).lower()
			if (skip == 'yes') or (skip == 'y'):
				return
		sock = urllib.urlopen(photoUri)
		self.saveImage(sock.read(), filename)
		sock.close()
			
						
	def saveImage(self, image, filename):
		print 'Writing %s' % filename
		imagefile = open(filename, 'w')
		imagefile.write(image)



##########################################
def usage():
##########################################
# Print usage
##########################################
	print """
	usage: download  [-d DIRECTORY] [-p PHOTONAME] 
		[-a ALBUMNAME] [-s SAVEAS]
		[-u|--user USERNAME]

	Required: (-p and/or -a) and -u
	Notes:
		If no albumname given, will search filenames and 
			tags for photoname given.
		Filename used with -s option cannot include '[' or ']'.
		Directory defaults to '.'	
		"""

	
if __name__ == "__main__":
	if (len(sys.argv) < 2):
		usage()
		sys.exit(2)
	args = 	gather_arguments(sys.argv[1:])
	client = client.Client(args['_user'] + '@gmail.com')
	if (args.has_key('_pass')):
		client.autologin(args['_pass'])
	else:
		client.login()
	downloader = Downloader(client, args)
	downloader.getPhotoEntries()
	downloader.getAllImages()
	
